﻿using System;
using System.Json;
using System.Linq;
using ToodledoAPI.DataTypes;
using ToodledoAPI.Exceptions;
namespace ToodledoAPI
{
    public static class goals
    {
        public static void get(Key key, Action<Goal[]> returnAction)
        {
            string Method = String.Format("goals/get.php?key={0}", key);
            ApplicationConfiguration.CallWebService(Method, (s) =>
            {
                if (s.IsToodledoException())
                {
                    throw new goalException(s);
                }
                JsonArray Array = (JsonArray)JsonObject.Parse(s);
                returnAction(Array.Select((F) => new Goal((JsonObject)F)).ToArray());
            });
        }

        public static void add(Key key, Action<Goal> returnAction, string name, int level = 0, int contributes = 0)
        {
            string Method = "goals/add.php?";
            if (level == 0 && contributes == 0)
                Method += String.Format("name={0};key={1}", name, key);
            else if (level == 0)
                Method += String.Format("name={0};contributes={1};key={2}", name, contributes, key);
            else if (contributes == 0)
                Method += String.Format("name={0};level={1};key={2}", name, level, key);
            else
                Method += String.Format("name={0};level={1};contributes={2};key={3}", name, level, contributes, key);

            ApplicationConfiguration.CallWebService(Method, (s) => returnAction(new Goal(s)));
        }

        public static void edit(Key key, int id, Action<Goal> returnAction, 
            string name = null, 
            int? level = null, 
            int? contributes = null, 
            bool? archived = null)
        {
            string Method = String.Format("goals/edit.php?key={0};id={1}", key, id);
            if (Helpers.AllNull(name,level,contributes,archived))
                return;
            if (name != null)
                Method += String.Format(";name={0}", name);
            if (level != null)
                Method += String.Format(";level={0}", level);
            if (contributes != null)
                Method += String.Format(";contributes={0}", contributes);
            if (archived != null)
                Method += String.Format(";archived={0}", archived);

            ApplicationConfiguration.CallWebService(Method, (s) => returnAction(new Goal(s)));
        }

        public static void delete(int id, Key key, Action<int> returnAction_Success)
        {
            string Method = String.Format("goals/delete.php?id={0};key={1}", id, key);
            ApplicationConfiguration.CallWebService(Method, (s) =>
            {
                if (s.IsToodledoException())
                {
                    throw new goalException(s);
                }
                returnAction_Success(int.Parse(((JsonObject)JsonObject.Parse(s))["deleted"]));
            });
        }
    }
    namespace DataTypes
    {
        public class Goal
        {
            public Goal(string s)
            {
                if (s.IsToodledoException())
                    throw new goalException(s);
                Load((JsonObject)JsonObject.Parse(s));
            }
            public Goal(JsonObject G)
            {
                Load(G);
            }
            void Load(JsonObject G)
            {
                id = int.Parse(G["id"]);
                name = G["name"];
                level = int.Parse(G["level"]);
                isArchived = G["archived"] == "1";
                contributes = int.Parse(G["contributes"]);
                note = G["note"];
            }

            public int id { get; set; }
            /// <summary>
            /// A text string up to 255 characters
            /// </summary>
            public string name { get; set; }
            /// <summary>
            /// The Level:
            /// 0=livetime
            /// 1=long-term
            /// 2=short-term
            /// </summary>
            public int level { get; set; }
            /// <summary>
            /// True if the goal is archived
            /// </summary>
            public bool isArchived { get; set; }
            /// <summary>
            /// The id number of a higher level goal that this one contributes to
            /// </summary>
            public int contributes { get; set; }
            public string note { get; set; }
        }
    }
}
